import { _decorator } from "cc";
import { Entity } from "./Entity";
import { AnimatorParam } from "../enums/AnimatorParam";
import { Direction } from "../enums/Direction";
import { EventType } from "../enums/EventType";
import { eventDispatcher } from "../Constants";
const { ccclass } = _decorator;

@ccclass("WoodenSkeleton")
export class WoodenSkeleton extends Entity {

    protected registerEvents(): void {
        eventDispatcher.on(EventType.PLAYER_MOVE_END, this.onPlayerMoveEnd, this);
        eventDispatcher.on(EventType.ATTACK_ENEMY, this.onAttack, this);
    }

    private onPlayerMoveEnd(x: number, y: number): void {
        if (this.state === Entity.State.DEATH) {
            return;
        }

        this.updateDirection(x, y);
        if (this.checkCanAttack(x, y)) {
            this.attack();
        }
    }

    private onAttack(id: number): void {
        if (id === this.id) {
            this.state = Entity.State.DEATH;
            eventDispatcher.emit(EventType.ENEMY_DEATH, id);
        }
    }

    private updateDirection(playerX: number, playerY: number, force: boolean = false): void {
        const offsetX = playerX - this.x;
        const offsetY = playerY - this.y;
        if (offsetX === offsetY && !force) {
            return;
        }

        let direction = this.direction;
        if (Math.abs(offsetX) < Math.abs(offsetY)) {
            direction = offsetY > 0 ? Direction.BOTTOM : Direction.TOP;
        } else {
            direction = offsetX > 0 ? Direction.RIGHT : Direction.LEFT;
        }
        if (direction !== this.direction) {
            this.direction = direction;
            this._animationController.setValue(AnimatorParam.STEP, true);
        }
    }

    private checkCanAttack(playerX: number, playerY: number): boolean {
        const distanceX = Math.abs(playerX - this.x);
        const distanceY = Math.abs(playerY - this.y);
        if (distanceX + distanceY === 1) {
            return true;
        }
        return false;
    }

    private attack(): void {
        this.state = Entity.State.ATTACK;
        eventDispatcher.emit(EventType.ATTACK_PLAYER);
    }
}